<script setup>
import { Page } from '@vben/common-ui';
import { updatePreferences } from '@vben/preferences';
import { computed, nextTick, onMounted, onUnmounted, ref } from 'vue';
import { useRouter } from 'vue-router';
import { useUserStore } from '@vben/stores';
import { requestClient } from '#/api/request.js';
import { Col, Row, Select } from 'ant-design-vue';
import useDraw from '../useDraw.js';
// 图表组件
import columnarBalloon from './components/columnarBalloon.vue';
import columnarFolding from './components/columnarFolding.vue';
import horizontalColumnar from './components/horizontalColumnar.vue';
import horizontalScreeningColumnar from './components/horizontalScreeningColumnar.vue';
import pieChart from './components/pieChart.vue';
import radar from './components/radar.vue';
import ranking from './components/ranking.vue';
// import getmark from '../w'

const { appRef, calcRate, windowDraw, unWindowDraw } = useDraw();
const router = useRouter();
const userStore = useUserStore();

// 判断是否是管理员
const isAdmin = computed(() => {
  return userStore.$state.userRoles?.some(role => role === 'superadmin');
});
// 企业列表
let userList = ref([])
// 接口加载状态
let loading = ref(false)
// 企业ID
let enterpriseId = ref(null)
// 组织列表
let orgList = ref([])
// 标题
let title = ref('京彩E家人客户端数据统计')
// 阅读趋势类型
let readingTrendType = [
  { name: '阅读时长趋势图', type: 1 },
  { name: '阅读人数趋势图', type: 2 },
  { name: '阅读本数趋势图', type: 3 },
  { name: '阅读章节趋势图', type: 4 },
]
// 阅读趋势类型
let activeReadingTrendType = ref(1);
// 阅读趋势组织
let readingTrendOrgId = ref(0)
// 阅读趋势数据
let readingTrendData = ref([])
// 用户统计趋势数据
let userStaticData = ref({})
// 受欢迎书籍组织
let popularBooksOrgId = ref(0)
// 受欢迎书籍数据
let popularBooksData = ref([])
// 各类书籍组织
let allKindsBooksOrgId = ref(0)
// 各类书籍数据
let allKindsBooksData = ref({
  chartData: [],
  indicators: []
})
// 阅读时长类型
let readingDurationTypes = ref([
  { id: 'Individual', name: '个人阅读时长' },
  { id: 'Organization', name: '组织阅读时长' },
])
// 激活的阅读时长类型
let activeReadingDurationType = ref('Individual')
// 阅读时长数据
let readingDurationData = ref([])
// 积分类型组织
let pointsOrgId = ref(0)
// 积分类型
let pointsTypes = ref([
  { id: 'Individual', name: '个人积分排行' },
  { id: 'Organization', name: '组织积分排行' },
])
// 积分类型数据
let pointsData = ref([])
// 激活积分类型
let activePointsType = ref('Individual')
// 组织积分组织
let organizationalPointsOrgId = ref(0)
// 组织积分数据
let organizationalPointsData = ref({
  xData: [],
  seriesData: []
})
let setTimeOutTimer = ref(86400000)

// 定时器句柄
const timerHandles = {
  readingTrend: null,
  userStatic: null,
  popularBooks: null,
  allKindsBooks: null,
  readingDuration: null,
  points: null,
  organizationalPoints: null,
};

// 清除所有定时器
function clearAllTimers() {
  Object.keys(timerHandles).forEach(key => {
    if (timerHandles[key]) {
      clearTimeout(timerHandles[key]);
      timerHandles[key] = null;
    }
  });
}

// 启动指定接口的定时器
function startTimer(key, fn) {
  if (timerHandles[key]) clearTimeout(timerHandles[key]);
  timerHandles[key] = setTimeout(() => {
    fn();
    startTimer(key, fn); // 递归定时
  }, setTimeOutTimer.value);
}

// 接口区域
// 获取用户列表
const getUserList = async () => {
  const res = await requestClient.get('/system/user/list');
  userList.value = res.rows.filter((item) => item.userId !== 1);
};
// 获取组织列表
const getOrgList = async () => {
  let params = {};
  if (isAdmin.value && enterpriseId.value) {
    params.enterpriseId = enterpriseId.value;
  }
  const res = await requestClient.get('/appA/getOrgList', { params })
  orgList.value = [
    { value: 0, label: '全部' },
    ...res.orgList.map((org) => ({
      value: org.orgId,
      label: org.orgName,
    })),
  ];
}
// 获取阅读趋势
const getReadingTrend = async () => {
  const params = {
    type: activeReadingTrendType.value,
    orgId: readingTrendOrgId.value,
  };
  if (isAdmin.value && enterpriseId.value) {
    params.enterpriseId = enterpriseId.value;
  }
  let res = await requestClient.post('/appA/readTime', params)
  readingTrendData.value = {
    xAxis: res.xaxis.map((item) => item + '月'),
    barData: res.barData,
    lineData: res.lineData,
  }
}
// 用户数据统计
const getUserStatic = async () => {
  const params = {};
  // 如果是管理员且选择了企业，添加企业ID参数
  if (isAdmin.value && enterpriseId.value) {
    params.enterpriseId = enterpriseId.value;
  }
  const res = await requestClient.get('/appA/numberOfUsers', { params })
  userStaticData.value = res
}
// 受欢迎书籍
const getPopularBooks = async () => {
  let params = {}
  // 如果是管理员且选择了企业，添加企业ID参数
  if (isAdmin.value && enterpriseId.value) {
    params.enterpriseId = enterpriseId.value;
  }
  const res = await requestClient.get('/appA/top30' + '/' + popularBooksOrgId.value, { params })
  popularBooksData.value = {
    books: res.books.slice(0, 15),
    values: res.values.slice(0, 15),
  };
}
// 各类书籍
const getAllKindsBooks = async () => {
  let params = {}
  // 如果是管理员且选择了企业，添加企业ID参数
  if (isAdmin.value && enterpriseId.value) {
    params.enterpriseId = enterpriseId.value;
  }
  const res = await requestClient.get('/appA/bookTypeRead' + '/' + allKindsBooksOrgId.value, { params })
  allKindsBooksData.value = {
    chartData: res.chartData,
    indicators: res.indicators,
  };
}
// 获取阅读时长
const getReadingDuration = async () => {
  let params = {}
  let tableType = activeReadingDurationType.value === 'Individual' ? 1 : 2;
  // 如果是管理员且选择了企业，添加企业ID参数
  if (isAdmin.value && enterpriseId.value) {
    params.enterpriseId = enterpriseId.value;
  }
  const res = await requestClient.get('/appA/readTimeTable' + '/' + tableType, { params })
  readingDurationData.value = res.rankingData
}
// 获取积分排行数据
const getActivePointsData = async () => {
  let params = {}
  let tableType = activePointsType.value === 'Individual' ? 1 : 2;
  // 如果是管理员且选择了企业，添加企业ID参数
  if (isAdmin.value && enterpriseId.value) {
    params.enterpriseId = enterpriseId.value;
  }
  const res = await requestClient.get('/appA/leaderBoardTable' + '/' + tableType, { params })
  pointsData.value = res.rankingData;
}
// 获取组织积分数据
const getOrganizationalPointsData = async () => {
  let params = {}
  // 如果是管理员且选择了企业，添加企业ID参数
  if (isAdmin.value && enterpriseId.value) {
    params.enterpriseId = enterpriseId.value;
  }
  const res = await requestClient.get('/appA/integralTrend' + '/' + organizationalPointsOrgId.value, { params })
  organizationalPointsData.value = {
    xData: res.xdata,
    seriesData: res.seriesData,
  }
}

// 更改阅读趋势类型
const changeReadingTrendType = (chartType) => {
  clearTimeout(timerHandles.readingTrend);
  activeReadingTrendType.value = chartType;
  getReadingTrend();
  startTimer('readingTrend', getReadingTrend);
}
// 更改阅读趋势组织
const changeReadingTrendOrgId = () => {
  clearTimeout(timerHandles.readingTrend);
  getReadingTrend();
  startTimer('readingTrend', getReadingTrend);
}
// 更改受欢迎书籍组织
const changePopularBooksOrgId = () => {
  clearTimeout(timerHandles.popularBooks);
  getPopularBooks();
  startTimer('popularBooks', getPopularBooks);
}
// 更改各类书籍组织
const changeAllKindsBooksOrgId = () => {
  clearTimeout(timerHandles.allKindsBooks);
  getAllKindsBooks();
  startTimer('allKindsBooks', getAllKindsBooks);
}
// 更改阅读时长类型
const changeReadingDurationType = (id) => {
  clearTimeout(timerHandles.readingDuration);
  activeReadingDurationType.value = id;
  getReadingDuration();
  startTimer('readingDuration', getReadingDuration);
}
// 更改积分排行类型
const changeActivepointsType = (id) => {
  clearTimeout(timerHandles.points);
  activePointsType.value = id;
  getActivePointsData();
  startTimer('points', getActivePointsData);
}
// 更改组织积分组织
const changeOrganizationalPoints = () => {
  clearTimeout(timerHandles.organizationalPoints);
  getOrganizationalPointsData();
  startTimer('organizationalPoints', getOrganizationalPointsData);
}

// 切换企业
const handleEnterpriseChange = async () => {
  initAPI();
}
// 是否获取企业列表
const isGetEnterpriseListHandler = async () => {
  if (isAdmin.value) {
    await getUserList();
    enterpriseId.value = userList?.value[0]?.enterpriseId;
  }
};
// 初始化页面调用接口
const initAPI = async () => {
  clearAllTimers();
  await Promise.all([
    getReadingTrend(),
    getUserStatic(),
    getPopularBooks(),
    getAllKindsBooks(),
    getReadingDuration(),
    getActivePointsData(),
    getOrganizationalPointsData()
  ]);
  // 初始化后分别启动定时器
  startTimer('readingTrend', getReadingTrend);
  startTimer('userStatic', getUserStatic);
  startTimer('popularBooks', getPopularBooks);
  startTimer('allKindsBooks', getAllKindsBooks);
  startTimer('readingDuration', getReadingDuration);
  startTimer('points', getActivePointsData);
  startTimer('organizationalPoints', getOrganizationalPointsData);
}

// 初始化页面配置
const pageInitializeHandler = async () => {
  calcRate();
  windowDraw();
  window.addEventListener('keydown', handleEscKeydown);
  await updateScreenPreferences('full');
}
// 按esc键退出
const handleEscKeydown = (event) => {
  if (event.key === 'Escape') {
    router.back();
    updateScreenPreferences('default');
  }
}
// 页面配置方法
const updateScreenPreferences = async (mode) => {
  return updatePreferences({
    app: { layout: mode === 'full' ? 'full-content' : 'sidebar-nav' },
    header: { enable: mode !== 'full' },
    sidebar: { collapsed: mode === 'full' },
    tabbar: { enable: false },
  });
}

onMounted(async () => {
  loading.value = true
  await isGetEnterpriseListHandler()
  await getOrgList()
  await initAPI()
  nextTick(() => {
    if (appRef.value) {
      pageInitializeHandler()
    }
  });
  
  // const { watermark } = getmark();
  // watermark("京彩E家人小程序数据分析");
  loading.value = false
})
// 页面卸载时清除所有定时器
onUnmounted(() => {
  clearAllTimers();
  window.removeEventListener('keydown', handleEscKeydown);
  // unWindowDraw();
});
</script>

<template>
  <Page :auto-content-height="true" class="map-container">
    <div id="map-box" ref="appRef">
      <div class="bg">
        <dv-loading v-if="loading">Loading...</dv-loading>
        <div v-else style="width: 100%; height: 100%">
          <div class="header">
            <div class="move-line"></div>
            <div class="header-title">{{ title }}</div>
            <img class="header-bg" src="../../../assets/header-04.png" />
            <div style="position: absolute;top: 2px;">
              <div class="scifi-select">
                <Select style="width: 120px;" v-if="isAdmin" v-model:value="enterpriseId" placeholder="请选择企业"
                  @change="handleEnterpriseChange" class="custom-select" dropdownClassName="scifi-select-dropdown">
                  <Select.Option v-for="org in userList" :key="org.userId" :value="org.enterpriseId">
                    {{ org.nickName }}
                  </Select.Option>
                </Select>
              </div>
            </div>
          </div>
          <Row :gutter="[10, 10]" style="height: calc(100% - 60px); padding: 10px 0">
            <Col :span="24" class="h-2/3">
            <Row :gutter="10" style="width: 100%; height: 100%;">
              <Col :span="16">
              <dv-border-box-13 class="p-2.5">
                <div class="chart-header">
                  <div class="chart-types">
                    <div v-for="chart in readingTrendType" :key="chart.type" class="chart-type-item"
                      :class="{ active: activeReadingTrendType === chart.type }" @click="
                        changeReadingTrendType(chart.type)
                        ">
                      {{ chart.name }}
                    </div>
                  </div>
                  <div class="scifi-select">
                    <Select style="width: 120px;" v-model:value="readingTrendOrgId" placeholder="请选择组织"
                      @change="changeReadingTrendOrgId" class="custom-select" dropdownClassName="scifi-select-dropdown">
                      <Select.Option v-for="org in orgList" :key="org.value" :value="org.value">
                        {{ org.label }}
                      </Select.Option>
                    </Select>
                  </div>
                </div>
                <columnarFolding :height="400" :chart-data="readingTrendData" />
              </dv-border-box-13>
              </Col>
              <Col :span="8">
              <div :span="24" style="padding-bottom: 10px;" class="h-1/2">
                <dv-border-box-8>
                  <div class="chart-header">
                    <div>激活人数和会员人数统计</div>
                  </div>
                  <horizontalColumnar :chart-data="userStaticData" />
                </dv-border-box-8>
              </div>
              <div :span="24" style="padding-top: 10px;" class="h-1/2">
                <dv-border-box-8>
                  <div class="chart-header">
                    <div>受欢迎书籍TOP15</div>
                    <div class="scifi-select">
                      <Select style="width: 120px;" v-model:value="popularBooksOrgId" placeholder="请选择组织"
                        @change="changePopularBooksOrgId" class="custom-select"
                        dropdownClassName="scifi-select-dropdown">
                        <Select.Option v-for="org in orgList" :key="org.value" :value="org.value">
                          {{ org.label }}
                        </Select.Option>
                      </Select>
                    </div>
                  </div>
                  <horizontalScreeningColumnar :chart-data="popularBooksData" />
                </dv-border-box-8>
              </div>
              </Col>
            </Row>
            </Col>

            <Col :span="24" class="h-1/3">
            <Row :gutter="10" style="width: 100%; height: 100%;">
              <Col :span="6">
              <dv-border-box-8>
                <div class="chart-header">
                  <div>各类书籍阅读情况</div>
                  <div class="scifi-select">
                    <Select style="width: 120px;" v-model:value="allKindsBooksOrgId" placeholder="请选择组织"
                      @change="changeAllKindsBooksOrgId" class="custom-select"
                      dropdownClassName="scifi-select-dropdown">
                      <Select.Option v-for="org in orgList" :key="org.value" :value="org.value">
                        {{ org.label }}
                      </Select.Option>
                    </Select>
                  </div>
                </div>
                <radar v-if="allKindsBooksData.chartData.length && allKindsBooksData.indicators.length"
                  :chart-data="allKindsBooksData" />
              </dv-border-box-8>
              </Col>
              <Col :span="6">
              <dv-border-box-8>
                <div class="p-2">
                  <div class="chart-types">
                    <div v-for="chart in readingDurationTypes" :key="chart.id" class="chart-type-item"
                      :class="{ active: activeReadingDurationType === chart.id }"
                      @click="changeReadingDurationType(chart.id)">
                      {{ chart.name }}
                    </div>
                  </div>
                </div>
                <ranking :type="activeReadingDurationType === 'Individual' ? 'personal' : 'organization'"
                  :title="activeReadingDurationType === 'Individual' ? '个人阅读时长排行' : '组织阅读时长排行'"
                  :data="readingDurationData" />
              </dv-border-box-8>
              </Col>
              <Col :span="6">
              <dv-border-box-8>
                <div class="p-2">
                  <div class="chart-types">
                    <div v-for="chart in pointsTypes" :key="chart.id" class="chart-type-item"
                      :class="{ active: activePointsType === chart.id }" @click="changeActivepointsType(chart.id)">
                      {{ chart.name }}
                    </div>
                  </div>
                </div>
                <pieChart v-if="pointsData.length" :type="activePointsType === 'Individual'
                  ? 'personal'
                  : 'organization'
                  " :chart-data="pointsData" />
              </dv-border-box-8>
              </Col>
              <Col :span="6">
              <dv-border-box-8>
                <div class="chart-header">
                  <div>组织积分趋势</div>
                  <div class="scifi-select">
                    <Select style="width: 120px;" v-model:value="organizationalPointsOrgId" placeholder="请选择组织"
                      @change="changeOrganizationalPoints" class="custom-select"
                      dropdownClassName="scifi-select-dropdown">
                      <Select.Option v-for="org in orgList" :key="org.value" :value="org.value">
                        {{ org.label }}
                      </Select.Option>
                    </Select>
                  </div>
                </div>
                <columnarBalloon :chart-data="organizationalPointsData" />
              </dv-border-box-8>
              </Col>
            </Row>
            </Col>
          </Row>
        </div>
      </div>
    </div>
  </Page>
</template>




<style lang="scss" scoped>
.chart-header {
  box-sizing: border-box;
  display: flex;
  align-items: center;
  justify-content: space-between;
  padding: 12px;
  border-radius: 4px;
}


.chart-types {
  display: flex;
  gap: 20px;

  .chart-type-item {
    position: relative;
    padding: 8px 16px;
    overflow: hidden;
    font-size: 14px;
    color: rgb(0 242 254 / 70%);
    cursor: pointer;
    border: 1px solid transparent;
    border-radius: 4px;
    transition: all 0.3s ease;

    &::before {
      position: absolute;
      top: 0;
      left: -100%;
      width: 100%;
      height: 2px;
      content: '';
      background: linear-gradient(90deg, transparent, rgb(0 242 254 / 80%));
      transition: 0.5s;
    }

    &:hover {
      color: rgb(0 242 254 / 100%);
      border-color: rgb(0 242 254 / 30%);
      box-shadow: 0 0 10px rgb(0 242 254 / 10%);

      &::before {
        left: 100%;
      }
    }

    &.active {
      color: #fff;
      background: linear-gradient(90deg,
          rgb(0 242 254 / 30%) 0%,
          rgb(0 242 254 / 10%) 100%);
      border-color: rgb(0 242 254 / 50%);
      box-shadow: 0 0 15px rgb(0 242 254 / 20%);
    }
  }
}

.map-container {
  width: 100%;
  height: 100%;
  padding: 0 !important;
  margin: 0 !important;
  background-color: black;

  #map-box {
    position: absolute;
    top: 50%;
    left: 50%;
    width: 1920px;
    height: 1080px;
    color: #d3d6dd;
    background-color: #ffebcd;
    transform: translate(-50%, -50%);
    transform-origin: left top;

    .bg {
      box-sizing: border-box;
      width: 100%;
      height: 100%;
      padding: 12px 12px 0;
      background-image: url('../../../assets/pageBg.png');
      background-position: center center;
      background-size: cover;
    }
  }
}

.header {
  position: relative;
  width: 100%;
  height: 50px;

  @keyframes move-left-to-right {
    from {
      transform: translateX(0);
    }

    to {
      transform: translateX(calc(100vw - 106px));
    }
  }

  .move-line {
    position: absolute;
    bottom: -11px;
    left: 0;
    width: 106px;
    height: 28px;
    background: url('../../../assets/line-bg.png') no-repeat;
    background-size: 100% 100%;
    animation: move-left-to-right 4s linear infinite;
  }

  .header-title {
    min-width: 250px;
    margin: 0 50px;
    font-size: 20px;
    font-weight: 900;
    line-height: 2.8rem;
    color: transparent;
    text-align: center;
    letter-spacing: 4px;
    background-image: linear-gradient(92deg,
        #0072ff 0%,
        #00eaff 48.8525%,
        #01aaff 100%);
    background-clip: text;
  }

  .header-bg {
    position: absolute;
    top: 0;
    right: 0;
    left: 0;
    z-index: 0;
    width: 100%;
    height: 3.84rem;
    margin: 0 auto;
  }
}


/* 科幻风 Select 样式 */
.scifi-select ::v-deep(.ant-select-selector) {
  background: linear-gradient(135deg, #0f2027 0%, #2c5364 100%);
  border: 2px solid #00ffe7;
  color: #00ffe7;
  border-radius: 8px;
  transition: border 0.3s;
}

.scifi-select ::v-deep(.ant-select-selector:hover),
.scifi-select ::v-deep(.ant-select-focused .ant-select-selector) {
  border-color: #ff00cc;
}

.scifi-select ::v-deep(.ant-select-arrow) {
  color: #00ffe7;
}

.scifi-select ::v-deep(.ant-select-dropdown) {
  background: #181c2b;
  border: 1.5px solid #00ffe7;
  min-width: 80px !important;
  width: 80px !important;
}

.scifi-select ::v-deep(.ant-select-item-option-selected) {
  background: linear-gradient(90deg, #00ffe7 0%, #ff00cc 100%);
  color: #181c2b;
}

.scifi-select ::v-deep(.ant-select-item-option-active) {
  background: rgba(0, 255, 231, 0.2);
}
</style>

<style lang="scss">
/* 简洁的下拉菜单样式 */
.scifi-select-dropdown.ant-select-dropdown {
  background: rgba(24, 36, 58, 0.95) !important;
  border: 1px solid #00eaff !important;
  border-radius: 4px !important;
  padding: 4px 0;
  min-width: 90px;
  max-width: 120px;
}

.scifi-select-dropdown .ant-select-item {
  color: rgba(0, 234, 255, 0.85) !important;
  font-size: 12px;
  font-family: 'Microsoft YaHei';
  border-radius: 2px;
  margin: 1px 2px;
  padding: 2px 6px;
  background: transparent !important;
  transition: all 0.2s;
  min-height: 22px !important;
  line-height: 1.2;
}

.scifi-select-dropdown .ant-select-item-option-active:not(.ant-select-item-option-disabled) {
  background: rgba(0, 114, 255, 0.1) !important;
  color: #fff !important;
}

.scifi-select-dropdown .ant-select-item-option-selected:not(.ant-select-item-option-disabled) {
  background: linear-gradient(90deg, #0072ff 0%, #00eaff 100%) !important;
  color: #fff !important;
  font-weight: 500;
}

.scifi-select-dropdown .ant-select-item-option-disabled {
  color: rgba(0, 234, 255, 0.3) !important;
  opacity: 0.6;
}

/* Select框本身的样式 */
.scifi-select ::v-deep(.ant-select-selector) {
  background: rgba(24, 36, 58, 0.8) !important;
  border: 1px solid #00eaff !important;
  border-radius: 4px !important;
  transition: all 0.3s;
  height: 28px !important;
  padding: 0 8px !important;
}

.scifi-select ::v-deep(.ant-select-selection-item) {
  color: rgba(0, 234, 255, 0.85) !important;
  font-size: 12px;
  line-height: 26px !important;
}

.scifi-select ::v-deep(.ant-select-arrow) {
  color: #00eaff;
  font-size: 12px;
}

.scifi-select ::v-deep(.ant-select-focused .ant-select-selector) {
  border-color: #00eaff !important;
}
</style>
